<template>
  <div class="tack-player-root">
    <lark-card border :radius="false" :show-title="false" body-width="25vw" body-height="20vh">
      <div class="bottomCard-body">
        <div class="bottomCard-body-header">
          <div class="bottomCard-body-header-operation">
            <div class="bottomCard-body-header-close" @click="exit">
              <i class="el-icon-error"></i>
            </div>
          </div>
        </div>
        <div class="t-p-b-container" v-if="!initFlag">
          <div class="t-p-row t-p-row-1">
            <div class="t-p-c">
              <div class="t-p-text t-p-label">轨迹点数</div>
              <div class="t-p-text t-p-value">{{total}}</div>
            </div>

            <div class="t-p-c">
              <div class="t-p-text t-p-label">方向</div>
              <div class="t-p-text t-p-value">
                <i class="el-icon-top" :style="anStyle"></i>
              </div>
            </div>

            <div class="t-p-c">
              <div class="t-p-text t-p-label">速度</div>
              <div class="t-p-text t-p-value">{{currentSpeed}}米/秒</div>
            </div>
          </div>

          <div class="t-p-row t-p-row-2">
            <div class="t-p-c">
              <div class="t-p-text t-p-label">时间</div>
              <div class="t-p-text t-p-value t-p-t-left">{{currentRecordTime}}</div>
            </div>
          </div>


          <div class="t-p-row t-p-row-3">
            <div class="t-p-c">
              <div class="t-p-text t-p-label">经纬度</div>
              <div class="t-p-text t-p-value t-p-t-left">{{currentX}},{{currentY}}</div>
            </div>
          </div>

          <div class="t-p-row t-p-row-3">
            <div class="t-p-c">
              <div class="t-p-text t-p-label">日期</div>
              <div class="t-p-text t-p-value t-p-t-left">
                <el-date-picker
                  v-model="time"
                  :disabled="!finishFlag"
                  type="datetimerange"
                  align="right"
                  start-placeholder="开始日期"
                  end-placeholder="结束日期"
                  :default-time="['00:00:00', '23:59:59']">
                </el-date-picker>
              </div>
            </div>
          </div>

          <div class="t-p-row t-p-row-4">
            <div class="t-p-c t-p-start">
              <div class="t-p-c-button-container bt-stop">
                <div class="t-p-c-button" @click="handle({ type:showing?HANDLE_TYPES.PAUSE:HANDLE_TYPES.START})">
                  <i class="fa fa-pause-circle-o" v-show="showing"></i>
                  <i class="fa fa-play-circle-o" v-show="!showing"></i>
                </div>
              </div>
            </div>
            <div class="t-p-c t-p-progress">
              <el-progress :text-inside="true" :stroke-width="20" :percentage="percentage"></el-progress>
            </div>
            <div class="t-p-c t-p-speed">
              <div class="t-p-c-button-container bt-retreat">
                <div class="t-p-c-button" @click="setSpeed(SPEED_TYPES.RETREAT)">
                  <i class="fa fa-backward"></i>
                </div>
              </div>
              <div class="t-p-text t-p-t-speed">
                {{speed}}
              </div>
              <div class="t-p-c-button-container bt-speed">
                <div class="t-p-c-button" @click="setSpeed(SPEED_TYPES.SPEED)">
                  <i class="fa fa-forward"></i>
                </div>
              </div>
              <div class="t-p-c-button-container bt-finish">
                <div class="t-p-c-button" @click="handle({ type:HANDLE_TYPES.FINISH})">
                  <i class="fa fa-stop-circle-o"></i>
                </div>
              </div>
            </div>
          </div>
        </div>
      </div>
    </lark-card>
  </div>
</template>

<script>
  import { reactive, toRefs, onMounted, ref, computed, watch } from '@vue/composition-api'
  import { Message, MessageBox } from 'element-ui'
  import store from '@/store'
  import router from '@/router'
  import { TackPlayback } from 'lark-map'
  import { getCurrentUser, getTack } from '@/api/industry/ctl'
  import { Loading } from 'element-ui'

  export default {
    name: 'index',
    props: {
      view: {
        type: Object,
        default: () => null
      },
      userId: {
        type: String,
        default: ''
      },
      initShow: {
        type: Boolean,
        default: false
      },
      millisec: {
        type: Number,
        default: 500
      }
    },
    components: {},
    setup(props, content) {

      let { view, userId } = props

      const HANDLE_TYPES = {
        RELOAD: 'reload',     //  重绘
        CLEAR: 'clear',       //  清除渲染
        PAUSE: 'pause',       //  暂停
        FINISH: 'finish',     //  结束
        RESIZE: 'resize',     //  倍数
        START: 'start',       //  开始
        RESET: 'reset'       //  重置放映参数
      }

      const SPEED_TYPES = {
        RETREAT: 'retreat',
        SPEED: 'speed'
      }

      const speedList = [0.5, 1, 1.25, 1.5, 2, 4]

      let currentData = new Date()
      let startData = new Date(`${currentData.getFullYear()}-${currentData.getMonth() + 1 >= 10 ? currentData.getMonth() + 1 : `0${currentData.getMonth() + 1}`}-${currentData.getDate() >= 10 ? currentData.getDate() : `0${currentData.getDate()}`} 00:00:00`)

      const anStyle = computed(() => {
        let { currentAngle } = data
        return { transform: `rotate(${currentAngle}deg)`, 'font-size': '20px' }
      })

      const data = reactive({
        tackPlayback: null,
        pageNum: 1,
        tackResult: [],
        HANDLE_TYPES,
        total: 0,
        initFlag: true,
        submitFlag: false,
        showing: false,
        finishFlag: false,
        SPEED_TYPES,
        speed: 1,
        loadingInstance: null,
        currentSpeed: 0,
        currentRecordTime: 0,
        currentAngle: 0,
        currentX: 0,
        currentY: 0,
        currentCount: 0,
        percentage: 0,
        anStyle,
        time: [startData, currentData]
      })

      const setSpeed = type => {
        let currentIndex = speedList.findIndex(item => item === data.speed)
        if (currentIndex < 0) return
        type === SPEED_TYPES.RETREAT ? currentIndex-- : currentIndex++
        data.speed = speedList[currentIndex] || data.speed
      }

      const random = (min, max) => {
        return Math.floor(Math.random() * (max - min)) + min
      }
      const dateFormat = (fmt, date) => {
        let ret
        const opt = {
          'Y+': date.getFullYear().toString(),        // 年
          'm+': (date.getMonth() + 1).toString(),     // 月
          'd+': date.getDate().toString(),            // 日
          'H+': date.getHours().toString(),           // 时
          'M+': date.getMinutes().toString(),         // 分
          'S+': date.getSeconds().toString()          // 秒
          // 有其他格式化字符需求可以继续添加，必须转化成字符串
        }
        for (let k in opt) {
          ret = new RegExp('(' + k + ')').exec(fmt)
          if (ret) {
            fmt = fmt.replace(ret[1], (ret[1].length == 1) ? (opt[k]) : (opt[k].padStart(ret[1].length, '0')))
          }
        }

        return fmt
      }

      const handle = ({ type = null, diploid = 1 }) => {
        if (!check() || !type || !data.tackPlayback[type]) return
        data.tackPlayback[type](diploid)
        data.finishFlag = type === HANDLE_TYPES.FINISH
        if (type === HANDLE_TYPES.START || type === HANDLE_TYPES.RELOAD) {
          data.showing = true
        } else if (type === HANDLE_TYPES.FINISH || type === HANDLE_TYPES.PAUSE) {
          data.showing = false
        }
      }

      const getTackData = async({ finish }) => {
        let pageSize = 500

        let { userId } = props

        if (finish) {
          data.pageNum = 1
          pageSize = data.total
        }

        let currentTotal = 0

        if (data.tackResult?.length) {
          data.tackResult.forEach(item => {
            currentTotal += item.length
          })
        }
        if ((currentTotal >= data.total || data.pageNum >= Math.ceil(data.total / pageSize)) && data.total > 0 && data.tackResult?.length) {
          let bufferRes = JSON.parse(JSON.stringify(data.tackResult))
          data.pageNum = 1
          return bufferRes
        }

        let queryParams = {
          pageSize,
          pageNum: data.pageNum++,
          userId,
          startDate: dateFormat('YYYY-mm-dd HH:MM:SS', data.time[0]),
          endDate: dateFormat('YYYY-mm-dd HH:MM:SS', data.time[1])
        }

        let { rows: tackData, total } = await getTack(queryParams)
        tackData = tackData.filter(item => item.latitude != null && item.longitude != null)
        if (!tackData?.length || !total) {
          return []
        }

        data.total = total

        tackData = tackData.sort((val1, val2) => {
          return new Date(val1.recordTime) - new Date(val2.recordTime)
        }).map(item => {
          let { longitude, latitude, recordTime, speed, angle } = item
          return { point: [longitude, latitude], attributes: { recordTime, speed, angle, test: random(1, 100) } }
        })

        let index = data.tackResult.length

        tackData.forEach(tDataItem => {

          if (!data.tackResult[index]) {
            data.tackResult.push([])
          }

          let currentItems = data.tackResult[index]

          let currentItem = currentItems[currentItems.length - 1]

          if (currentItem && Math.abs(((new Date(currentItem.attributes.recordTime) - new Date(tDataItem.attributes.recordTime)) / 1000 / 60)) > 4.5) {
            data.tackResult.push([])
            index++
          }

          data.tackResult[index].push(tDataItem)

        })

        data.initFlag = false

        return data.tackResult
      }

      const difference = ({ currentPoint, perPoint, currentIndex }) => {
        if (!currentPoint) return

        if (currentIndex + 1 >= data.total) {
          handle({ type: HANDLE_TYPES.RESET })
          handle({ type: HANDLE_TYPES.FINISH })
        }

        let { attributes: { speed, recordTime, angle }, point: [x, y] } = currentPoint

        let color = []

        if (speed >= 0 && speed < 2) {            //  步行
          color = [38, 234, 146, 1]
        } else if (speed >= 2 && speed < 4.5) {   //  自行车
          color = [105, 251, 88, 1]
        } else if (speed >= 4.5 && speed < 8) {   //  汽车慢行
          color = [232, 251, 38, 1]
        } else if (speed >= 8 && speed < 12) {   //  小于50迈
          color = [245, 177, 45, 1]
        } else {                                  // 大于50迈
          color = [250, 0, 0, 1]
        }

        let lineSymbol = {
          type: 'simple-line',
          color,
          width: 10
        }

        let bufferColor = JSON.parse(JSON.stringify(color))

        bufferColor[3] = 0.4

        let pointSymbol = {
          type: 'simple-marker',
          style: 'circle',
          size: 20,
          color: bufferColor,
          outline: {
            color,
            size: 20
          }
        }

        data.currentSpeed = speed
        data.currentRecordTime = recordTime
        data.currentAngle = angle
        data.currentX = x
        data.currentY = y
        data.currentCount = currentIndex
        data.percentage = parseFloat(((currentIndex + 1) / data.total * 100).toFixed(2))

        return { lineSymbol, pointSymbol }
      }

      const finishEndFunction = () => {

        if (data.loadingInstance) {
          data.loadingInstance.close()
          data.showing = false
          debugger
          data.finishFlag = true

          let lastItem = data.tackResult[data.tackResult.length - 1]
          let { attributes: { speed, recordTime, angle }, point: [x, y] } = lastItem[lastItem.length - 1]

          data.currentSpeed = speed
          data.currentRecordTime = recordTime
          data.currentAngle = angle
          data.currentX = x
          data.currentY = y
          data.currentCount = data.tackResult.length - 1
          data.percentage = 100
          data.tackResult = []
        }
      }

      const finishStartFunction = () => {
        data.loadingInstance = Loading.service({ fullscreen: true })
      }

      const initTackPlayBack = () => {
        data.initFlag = true
        data.total = 0

        getCurrentUser(props.userId).then(res => {

          let { nickname: animationText } = res

          let { millisec } = props

          data.tackPlayback = new TackPlayback({
            getTackData,
            view,
            residue: 100,
            textKey: 'recordTime',
            difference,
            animationSymbol: {
              type: 'picture-marker',
              url: '',
              width: 24,
              height: 24
            },
            animationText,
            drawProcessPoint: false,
            finishEndFunction,
            finishStartFunction,
            angleKey: 'angle',
            millisec: millisec || 1000
          })
        })
      }

      const check = () => {
        let res = true
        if (!data.time?.length || data.time[0] > data.time[1]) {
          Message.error('请选择正确的日期')
          res = false
        }
        if (!props.view || !data.tackPlayback || !props.userId || props.userId === '') {
          Message.error('该人员没有轨迹')
          res = false
        }
        return res
      }

      const finish = () => {
        if (data.tackPlayback) {
          handle({ type: HANDLE_TYPES.PAUSE })
          handle({ type: HANDLE_TYPES.RESIZE })
          handle({ type: HANDLE_TYPES.CLEAR })
          data.tackResult = []
          data.pageNum = 1
        }
      }

      const exit = () => {
        finish()
        content.emit('exit')
      }

      watch(() => data.initFlag, val => {
        if (!val) {
          setTimeout(() => {
            props.initShow && handle({ type: data.HANDLE_TYPES.START })
            if (!data.submitFlag) {
              content.emit('load', { finish })
              data.submitFlag = true
            }
          }, 5)
        }
      })

      watch(() => props.userId, (newVal, odlVal) => {
        let { view } = props
        if (!newVal || newVal !== '' || newVal !== odlVal) {
          if (data.tackPlayback) {
            finish()
          }
        } else if (view && newVal && newVal !== '' && newVal !== odlVal) {
          initTackPlayBack()
        }
      })

      watch(() => data.speed, diploid => {
        if (diploid < 0.5 || diploid > 4) return
        handle({ type: HANDLE_TYPES.RESIZE, diploid })
      })

      if (view && props.userId && props.userId !== '') {
        initTackPlayBack()
      }

      return { ...toRefs(data), handle, exit, setSpeed }
    }
  }
</script>

<style scoped lang="scss">
  $header-height: 20px;
  .tack-player-root {
    .bottomCard-body {
      display: flex;
      flex-direction: column;
      height: 100%;

      .bottomCard-body-header {
        display: flex;
        flex-direction: row;
        justify-content: space-between;
        height: $header-height;
        box-sizing: border-box;

        .bottomCard-body-header-operation {
          position: absolute;
          right: 10px;

          .bottomCard-body-header-close {
            margin-left: 20px;
            font-size: 20px;
            color: red;

            &:hover {
              cursor: pointer;
            }
          }
        }
      }

      .t-p-b-container {
        flex: 1;
        width: 100%;
        display: flex;
        flex-direction: column;
        padding: 10px;

        .t-p-row {
          height: 25%;
          width: 100%;
          display: flex;
          flex-direction: row;
          padding: 5px;

          .t-p-c {
            flex: 1;
            display: flex;
            flex-direction: row;

            .t-p-text {
              display: flex;
              flex-direction: row;
              justify-content: center;
              align-items: flex-end;

              &.t-p-label {
                width: max-content;
                margin-right: 10px;
              }

              &.t-p-value {
                text-align: center;

                &.t-p-t-left {
                  text-align: left;
                }
              }

              &.t-p-t-speed {
                height: 100%;
                flex: 1;
                display: flex;
                flex-direction: row;
                justify-content: center;
              }
            }


            .t-p-c-button-container, {
              height: 100%;
              flex: 1;
              display: flex;
              flex-direction: row;
              justify-content: center;
              align-items: center;

              .t-p-c-button {
                cursor: pointer;
                width: 36px;
                height: 30px;
                display: flex;
                flex-direction: column;
                justify-content: center;
                align-items: center;
                font-size: 30px;
              }
            }

            &.t-p-start {
              flex: 0;
              width: max-content;
              margin-right: 5px;
            }

            &.t-p-progress {
              width: 50%;
              display: flex;
              flex-direction: column;
              justify-content: center;
              align-items: center;

              .el-progress {
                width: 100%;
                display: flex;
                flex-direction: column;
                justify-content: center;
              }
            }

            &.t-p-speed {
              flex: 1;
              display: flex;
              flex-direction: row;
              justify-content: center;
            }
          }
        }
      }
    }
  }
</style>
<style lang="scss">
  .tack-player-root {
    .bottomCard-body {
      .bottomCard-body-header {
        .bottomCard-body-header-operation {
          .el-button.el-button--success.el-button--mini {
            padding-top: 5px;
            padding-bottom: 5px;
          }
        }
      }
    }
  }

  .el-picker-panel {
    .el-picker-panel__body-wrapper {
      .el-picker-panel__body {
        .el-input__inner {
          border-radius: 25px;
        }
      }
    }
  }
</style>
